<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html><head><meta http-equiv="Content-Type" content="text/html;charset=iso-8859-1">
<title>[Generic Component Framework v3] GCF Component Model</title>
<link href="doxygen.css" rel="stylesheet" type="text/css">
<!--link href="tabs.css" rel="stylesheet" type="text/css"-->
</head><body>
 <div id="wrapper">
    <div id="logo_box">
        <a class="img_link" href="https://github.com/pnudupa/gcf" target="_blank" ><img style="float:left;margin-left:10px;margin-top:5px;margin-bottom:5px;"src="header_gcf_logo.jpg" alt="GCF LOGO"/></a>
        <a class="img_link" href="https://www.vcreatelogic.com/" target="_blank" ><img style="float:right;margin-right:10px; margin-top: 30px;" src="header_vcl_logo.jpg" alt="VCL LOGO"/></a>
        <div style="clear:both"></div>
    </div>
    <div class="nav">
        <ul>
            <li class="selectedpage">
                <a class="a-home" href="index.html" >
                    <span>Home</span>
                </a>
            </li>
            <li>
                <a class="a-classes " href="classes.html">
                    <span>All Classes</span>
                </a>
            </li>
            <li>
                <a class="a-home " href="gcf_modules.html">
                    <span>Modules</span>
                </a>
            </li>
            <li>
                <a class="a-home " href="gcf_guides_and_videos.html">
                    <span>Guides & Videos</span>
                </a>
            </li>
            <li>
                <a class="a-home " href="gcf_tools_and_inbuilt_components.html">
                    <span>Tools & Components</span>
                </a>
            </li>
        </ul>
    </div>
    <div id="main-content">
        <div class="inside">
        <div>
<!-- Generated by Doxygen 1.8.16 -->
</div><!-- top -->
<div class="PageDoc"><div class="header">
  <div class="headertitle">
<div class="title">GCF Component Model </div>  </div>
</div><!--header-->
<div class="contents">
<div class="toc"><h3>Table of Contents</h3>
<ul><li class="level1"><a href="#gcf_component_model_1">What is a component model?</a></li>
<li class="level1"><a href="#gcf_component_model_2">GCF Component model</a></li>
<li class="level1"><a href="#gcf_component_model_3">Anatomy of the main() function of a GCF application</a><ul><li class="level2"><a href="#gcf_component_model_31">Creating an application instance</a></li>
<li class="level2"><a href="#gcf_component_model_32">The foundation component</a></li>
<li class="level2"><a href="#gcf_component_model_33">Figuring out the components to load</a></li>
<li class="level2"><a href="#gcf_component_model_34">Processing command-line arguments</a></li>
<li class="level2"><a href="#gcf_component_model_35">Triggering the event loop</a></li>
</ul>
</li>
<li class="level1"><a href="#gcf_component_model_4">Authoring GCF components</a></li>
<li class="level1"><a href="#gcf_component_model_5">How component loading works</a></li>
<li class="level1"><a href="#gcf_component_model_5_5">How component unloading works</a></li>
<li class="level1"><a href="#gcf_component_model_6">Registering objects</a><ul><li class="level2"><a href="#gcf_component_model_61">Component content file</a></li>
<li class="level2"><a href="#gcf_component_model_62">Using addContentObject() function</a></li>
<li class="level2"><a href="#gcf_component_model_63">Explicitly creating object-tree-nodes</a></li>
</ul>
</li>
<li class="level1"><a href="#gcf_component_model_7">Searching for objects</a><ul><li class="level2"><a href="#gcf_component_model_71">Using gFindObject and gFindObjects</a></li>
<li class="level2"><a href="#gcf_component_model_72">Connecting to nodeAdded() signal of gAppService-&gt;objectTree()</a></li>
</ul>
</li>
<li class="level1"><a href="#gcf_component_model_8">How application shut down works</a></li>
<li class="level1"><a href="#gcf_component_model_9">Suggested reading</a></li>
</ul>
</div>
<div class="textblock"><p>GCF (Generic Component Framework) is primarily a component-framework library. Its "killer feature" is a component model that you can leverage in your applications to build "pluggable" and extensible applications on Windows, Linux and Mac OS.</p>
<p>This page provides an overview of the component model offered by GCF. A clear understand of the the component model will allow you to powerfully make use of it in your applications.</p>
<h1><a class="anchor" id="gcf_component_model_1"></a>
What is a component model?</h1>
<p>A quick search on Google reveals this answer</p>
<p> 
<div style="border: solid; border-width: 2px; width: 50%; padding: 10px">
An architecture and an API that allows developers to define reusable segments of code that can be
combined to create a program.
</div>
</p>
<p>GCF offers exactly that! <em>GCF offers an architecture and an API that allows developers to define reusable segments of Qt code that can be combined to create Qt applications</em>.</p>
<p>This page explains architecture of the component model offered by GCF, with links to API (classes and methods) that implement the model.</p>
<h1><a class="anchor" id="gcf_component_model_2"></a>
GCF Component model</h1>
<p>GCF's component model comprises of two key concepts:</p>
<ul>
<li>Concept #1: <b>Component</b> - defined as an entity that plugs its objects and services into the application</li>
</ul>
<p>AND</p>
<ul>
<li>Concept #2: <b>Application</b> - defined as an entity that locates components for loading and loads them</li>
</ul>
<p>The concepts are captured and implemented in terms of</p>
<ul>
<li>A <a class="el" href="class_g_c_f_1_1_component.html">GCF::Component</a> class from which you can subclass and implement virtual functions, to "plug" your objects and services into the application.</li>
</ul>
<p>AND</p>
<ul>
<li>A <a class="el" href="class_g_c_f_1_1_application_services.html">GCF::ApplicationServices</a> instance, to allow you to load components after locating them.</li>
</ul>
<p>AND</p>
<ul>
<li>A bunch of helper classes like <a class="el" href="class_g_c_f_1_1_object_tree.html">GCF::ObjectTree</a>, <a class="el" href="class_g_c_f_1_1_object_list.html">GCF::ObjectList</a> and so on for capturing the data of the component model.</li>
</ul>
<p>Play the video below to get a sense of these concepts and how they come together in a GCF application.</p>
<p> 
<video width="500" controls>
    <source src="../../../Videos/Concepts/Component-Model.mp4" type="video/mp4">
</video>
<p>If you are unable to view the embedded video above, please click <a href="http://player.vimeo.com/video/77953239" target="_blank">here</a> to view it on the web.</p>
</p>
<p>If you are unable to view the video, the following bullet points summarize the content of the video.</p>
<p> 
<p>&nbsp;</p>
<table cellpadding="10" cellspacing="0" border="0"><tr><td>
 </p><ul>
<li>A GCF application begins with the instantiation of a subclass of <a class="el" href="class_g_c_f_1_1_application_services.html">GCF::ApplicationServices</a>. This could be a <a class="el" href="class_g_c_f_1_1_application.html">GCF::Application</a>, <a class="el" href="class_g_c_f_1_1_gui_application.html">GCF::GuiApplication</a> or <a class="el" href="class_g_c_f_1_1_qml_application.html">GCF::QmlApplication</a>.</li>
</ul>
<ul>
<li>Upon instantiation of the application, a <a class="el" href="class_g_c_f_1_1_object_tree.html">GCF::ObjectTree</a> instance is created. This is accessible via <a class="el" href="class_g_c_f_1_1_application_services.html#a22657bd136cbf7a285cf0b273a40963a">GCF::ApplicationServices::objectTree()</a> [ or <code>gAppService-&gt;objectTree()</code> ]</li>
</ul>
<ul>
<li>Initially the object tree has one node - called "Application Node". This node contains a pointer to the application instance.</li>
</ul>
<ul>
<li>Each node in the object tree is an instance of <a class="el" href="class_g_c_f_1_1_object_tree_node.html">GCF::ObjectTreeNode</a>.</li>
</ul>
<ul>
<li>Applications would then start loading components by calling the <a class="el" href="class_g_c_f_1_1_application_services.html#a9fe06a88ce3a56f825cd2e11be4b0cf0">GCF::ApplicationServices::loadComponent()</a> [ or <code>gAppService-&gt;loadComponent()</code> ] method.</li>
</ul>
<ul>
<li>Components themselves are subclasses of <a class="el" href="class_g_c_f_1_1_component.html">GCF::Component</a>. They can be loaded from shared-libraries or statically as well.</li>
</ul>
<ul>
<li>Upon loading of a component, a node for the same will get created in the object-tree under the "Application" node.</li>
</ul>
<ul>
<li>For each object that the component chooses to register, a node is created under the component's node in the object tree.  
</td><td>
 <div class="image">
<img src="gcf-component-model1.png" alt=""/>
</div>
  
</td></tr></table>
<p>&nbsp;</p>
</li>
</ul>
<p>Once all the components are loaded, the application's object tree would contain one sub-tree per component. Each of those sub-trees would contain one node for every object registered by the component with the application. Each node in the object-tree would contain a pointer to the <code>QObject</code> that they register.</p>
<p>The <a class="el" href="group__gcf__core.html#gae5dc3c84e9b39c247bf80f0be23c6c63">gFindObject</a> method allow searching of objects in the object tree. You can search for objects by</p>
<ul>
<li>their <b>path</b>, which is a dot (.) separated list of names from the "Application" node to the object's node.</li>
</ul>
<p>OR</p>
<ul>
<li>name of a class or interface that they implement</li>
</ul>
<p>Since registered objects are searchable, we call them "exposed" objects.</p>
<h1><a class="anchor" id="gcf_component_model_3"></a>
Anatomy of the main() function of a GCF application</h1>
<p>The code snippet below shows a typical <code>main()</code> function of a GCF application.</p>
<div class="fragment"><div class="line"><span class="preprocessor">#include &lt;GCF3/Application&gt;</span></div>
<div class="line"><span class="preprocessor">#include &lt;GCF3/Component&gt;</span></div>
<div class="line"> </div>
<div class="line"><span class="preprocessor">#include &quot;BaseComponent.h&quot;</span></div>
<div class="line"> </div>
<div class="line"><span class="keywordtype">int</span> main(<span class="keywordtype">int</span> argc, <span class="keywordtype">char</span> **argv)</div>
<div class="line">{</div>
<div class="line">    <a class="code" href="class_g_c_f_1_1_application.html">GCF::Application</a> a(argc, argv);</div>
<div class="line"> </div>
<div class="line">    <span class="comment">// Load the first foundation component of the application</span></div>
<div class="line">    <span class="comment">// In this code snippet, it is BaseComponent</span></div>
<div class="line">    BaseComponent *baseComponent = <span class="keyword">new</span> BaseComponent;</div>
<div class="line">    baseComponent-&gt;load();</div>
<div class="line"> </div>
<div class="line">    <span class="comment">// Figure out names of components to load</span></div>
<div class="line">    QStringList componentNames = getComponentNamesFromSomewhere();</div>
<div class="line"> </div>
<div class="line">    <span class="comment">// Load those components</span></div>
<div class="line">    a.loadComponents(componentNames);</div>
<div class="line"> </div>
<div class="line">    <span class="comment">// Process command-line arguments</span></div>
<div class="line">    a.processArguments();</div>
<div class="line"> </div>
<div class="line">    <span class="comment">// Look for arguments we are interested in</span></div>
<div class="line">    QVariantMap argsMap = a.argumentsMap();</div>
<div class="line">    QStringList args = argsMap.keys();</div>
<div class="line">    Q_FOREACH(QString arg, args)</div>
<div class="line">    {</div>
<div class="line">        <span class="comment">// if we interested in an arg,</span></div>
<div class="line">        <span class="comment">// then we can look for its value from the map</span></div>
<div class="line">        <span class="comment">// and process it.</span></div>
<div class="line">    }</div>
<div class="line"> </div>
<div class="line">    <span class="comment">// Run the event loop</span></div>
<div class="line">    <span class="keywordflow">return</span> a.exec();</div>
<div class="line">}</div>
</div><!-- fragment --><p>In the sub-sections below, each aspect of the <code>main()</code> function are explained in more detail.</p>
<h2><a class="anchor" id="gcf_component_model_31"></a>
Creating an application instance</h2>
<p>You will need to create an instance of <a class="el" href="class_g_c_f_1_1_application.html">GCF::Application</a> OR <a class="el" href="class_g_c_f_1_1_gui_application.html">GCF::GuiApplication</a> OR <a class="el" href="class_g_c_f_1_1_qml_application.html">GCF::QmlApplication</a> before any component is instantiated and loaded in the application.</p>
<ul>
<li>The <a class="el" href="class_g_c_f_1_1_application.html">GCF::Application</a> class is available from <a class="el" href="group__gcf__core.html">GCF Core Module</a>. You should create an instance of this class only if you are creating non-gui and console-only applications.</li>
</ul>
<ul>
<li>The <a class="el" href="class_g_c_f_1_1_gui_application.html">GCF::GuiApplication</a> class is available from <a class="el" href="group__gcf__gui.html">GCF Gui Module</a> module. You should create an instance of this class when you are creating a widgets application.</li>
</ul>
<ul>
<li>The <a class="el" href="class_g_c_f_1_1_qml_application.html">GCF::QmlApplication</a> class is available from <a class="el" href="group__gcf__quick.html">GCF Quick Module</a> module. You should create an instance of this class when you are creating a Qt-Quick application.</li>
</ul>
<p>In GCF, there is a macro called <a class="el" href="group__gcf__core.html#gAppService">gAppService</a> that always points to the <a class="el" href="class_g_c_f_1_1_application_services.html">GCF::ApplicationServices</a> part of a GCF application instance. There is a <a class="el" href="group__gcf__core.html#gApp">gApp</a> macro that always points to an instance of</p>
<ul>
<li><a class="el" href="class_g_c_f_1_1_application.html">GCF::Application</a> in console-only applications, </li>
<li><a class="el" href="class_g_c_f_1_1_gui_application.html">GCF::GuiApplication</a> in widgets applications and </li>
<li><a class="el" href="class_g_c_f_1_1_qml_application.html">GCF::QmlApplication</a> in Qt Quick applications</li>
</ul>
<p>The following diagram shows the class diagram of application classes in GCF.</p>
<div class="image">
<img src="gcf-application-classes.png" alt=""/>
</div>
<p>While <a class="el" href="class_g_c_f_1_1_application.html">GCF::Application</a>, <a class="el" href="class_g_c_f_1_1_gui_application.html">GCF::GuiApplication</a> and <a class="el" href="class_g_c_f_1_1_qml_application.html">GCF::QmlApplication</a> are direct subclasses of <a class="el" href="class_g_c_f_1_1_application_services.html">GCF::ApplicationServices</a>, they are all not direct subclasses of <code>QCoreApplication</code>.</p>
<p>Because of this class design, the macro <a class="el" href="group__gcf__core.html#gApp">gApp</a> would return a NULL pointer if </p><ul>
<li>you include <code>&lt;GCF3/Application&gt;</code> in a GUI or Qt Quick application</li>
</ul>
<p>OR</p>
<ul>
<li>you include <code>&lt;GCF3/GuiApplication&gt;</code> in a Qt quick or console application</li>
</ul>
<p>OR</p>
<ul>
<li>you include <code>&lt;GCF3/QmlApplication&gt;</code> in a widgets or console application.</li>
</ul>
<p>However, the macro <a class="el" href="group__gcf__core.html#gAppService">gAppService</a> would never be NULL if used in a GCF application.</p>
<h2><a class="anchor" id="gcf_component_model_32"></a>
The foundation component</h2>
<p>All GCF applications should ideally offer a "foundation component" after which all other componts are loaded. Though it not compulsory, we encourage you to not write "surrogate" applications that can be configured to load any GCF component.</p>
<p>Typically the "foundation component" would set the core personality of the application and offer core services. Auxiliary components can then extend the core application or build on top of the core services offered by the application to expand its business and technology possibility.</p>
<p>In a GUI application, the "foundation component" would offer a main-window with predefined panels, menus, tool-bars, dialog boxes and service-dictionaries on to which auxiliary components will merge their UI elements (widgets, actions, menus etc..) and service objects.</p>
<p>In a console-application, the "foundation component" would offer a set of core services, objects and service-dictionaries on to which auxiliary components will merge their service objects.</p>
<p>The <a class="el" href="gcf_component_model.html#gcf_component_model_6">section on registering objects</a> explains how object merging works.</p>
<h2><a class="anchor" id="gcf_component_model_33"></a>
Figuring out the components to load</h2>
<p>Once the "foundation component" is instantiated and loaded, you would want to load auxiliary components.</p>
<p>If component classes are statically linked into your application, then you can simply create an instance of those components and invoke the <a class="el" href="class_g_c_f_1_1_component.html#a06e3573f06292a5211b81201ced61deb">load()</a> method on them.</p>
<p>If your components are available for loading from shared libraries, then you can invent a mechanism to source the list of shared libraries that you want to load. You could for example</p>
<ul>
<li>read component names from an INI, XML or plain-text file and load them.</li>
</ul>
<p>OR</p>
<ul>
<li>read component names from the Windows Registry and load them. (Of-course this would work only on Microsoft Windows).</li>
</ul>
<p>OR</p>
<ul>
<li>make use of <code>QDirIterator</code> to iterate over all shared libraries in a predefined directory and load components from them.</li>
</ul>
<p>OR</p>
<ul>
<li>hard-code the component names to load in the <code>main()</code> function</li>
</ul>
<p>OR</p>
<ul>
<li>fetch names of components to load from a license file or from a web-service.</li>
</ul>
<p>Once you are clear about the set of components to load, you can make use of <a class="el" href="class_g_c_f_1_1_application_services.html#a9fe06a88ce3a56f825cd2e11be4b0cf0">GCF::ApplicationServices::loadComponent()</a> or <a class="el" href="class_g_c_f_1_1_application_services.html#a23b3dbefa1596550f6fa85bba4d8d63d">GCF::ApplicationServices::loadComponents()</a> to load the components.</p>
<h2><a class="anchor" id="gcf_component_model_34"></a>
Processing command-line arguments</h2>
<p>Users of your application can pass command-line arguments of the form <code>"-key:value"</code>. Such arguments can be captured into <a class="el" href="class_g_c_f_1_1_application_services.html#a7e69fc75a4845eb0b74f75e606d50fe9">argumentsMap()</a> and processed in the <code>main()</code> function by calling either</p>
<ul>
<li><a class="el" href="class_g_c_f_1_1_application_services.html#a0f82916833415a06831f097ab940e893">processArguments()</a> on the application object</li>
</ul>
<p>OR</p>
<ul>
<li><a class="el" href="class_g_c_f_1_1_application.html#ab9501117acd2cad8673c7a35f6b3b793">processArgumentsAndExec()</a> instead of <code>exec()</code> on the application object.</li>
</ul>
<p>By default, GCF processes the <code>-loadComponents:</code> command-line argument as a comma (,) separated list of component names. It then loads those components one after the other.</p>
<p>For example, users of your application could launch it from terminal like this</p>
<pre class="fragment">$ ./YourGCFApplication --loadComponents:Path1/Component1,Path2/Component2,Path3/Component3
</pre><p>This would cause your application to also load GCF components from <code>Path1/Component1</code>, <code>Path2/Component2</code> and <code>Path3/Component3</code> libraries. [<b>NOTE:</b> this would work only if you have explicitly invoked <a class="el" href="class_g_c_f_1_1_application_services.html#a0f82916833415a06831f097ab940e893">processArguments()</a> OR <a class="el" href="class_g_c_f_1_1_application.html#ab9501117acd2cad8673c7a35f6b3b793">processArgumentsAndExec()</a> on your application object in the <code>main()</code> function]</p>
<dl class="section note"><dt>Note</dt><dd>If you are going to make use of <a class="el" href="gcf_investigator.html">GCF Investigator</a> to record and/or run test-scripts, then you have to process arguments.</dd></dl>
<h2><a class="anchor" id="gcf_component_model_35"></a>
Triggering the event loop</h2>
<p>Finally, you should call the <code>exec()</code> (or <a class="el" href="class_g_c_f_1_1_application.html#ab9501117acd2cad8673c7a35f6b3b793">processArgumentsAndExec()</a>) function on the application object to trigger the event loop and actually "start" your application.</p>
<h1><a class="anchor" id="gcf_component_model_4"></a>
Authoring GCF components</h1>
<p>As stated before, a component in GCF is defined as an entity that plugs its objects into the application. Stated in another way, GCF components are basically factories of objects. They instantiate objects and register with the application. The actual process of registering objects is <a class="el" href="gcf_component_model.html#gcf_component_model_6">explained in a later section</a>.</p>
<p>Creating a component in GCF is simply a matter of subclassing from <a class="el" href="class_g_c_f_1_1_component.html">GCF::Component</a> or any of its subclasses like <a class="el" href="class_g_c_f_1_1_qml_component.html">GCF::QmlComponent</a> and <a class="el" href="class_g_c_f_1_1_gui_component.html">GCF::GuiComponent</a>. You can then instantiate it and invoke the <a class="el" href="class_g_c_f_1_1_component.html#a06e3573f06292a5211b81201ced61deb">GCF::Component::load()</a> function on it to load the component.</p>
<p>Instantiating the component is simply a matter of calling the component class's constructor, if the component class is linked into the application.</p>
<p>If the component class is available in a dynamically loadable library, then you can either</p>
<ul>
<li>call <a class="el" href="class_g_c_f_1_1_application_services.html#a2d00007fdb8de827c1d47aac03e0d09c">GCF::ApplicationServices::instantiateComponent()</a> and then <a class="el" href="class_g_c_f_1_1_component.html#a06e3573f06292a5211b81201ced61deb">GCF::Component::load()</a> on the component returned by it</li>
</ul>
<p>OR</p>
<ul>
<li>call <a class="el" href="class_g_c_f_1_1_application_services.html#a9fe06a88ce3a56f825cd2e11be4b0cf0">GCF::ApplicationServices::loadComponent()</a> to both instantiate and load the component from a library in one shot.</li>
</ul>
<p>For a component class to be loadable from a dynamically loadable library, you should make use of the <a class="el" href="group__gcf__core.html#GCF_EXPORT_COMPONENT">GCF_EXPORT_MACRO</a> macro to export the component. This macro must be written exactly once in a library and in a source file.</p>
<h1><a class="anchor" id="gcf_component_model_5"></a>
How component loading works</h1>
<p>Components can be loaded using any of the following means</p>
<ul>
<li>Create an instance of the component class and then call the <a class="el" href="class_g_c_f_1_1_component.html#a06e3573f06292a5211b81201ced61deb">load()</a> method. </li>
<li>Call the <a class="el" href="class_g_c_f_1_1_application_services.html#a9fe06a88ce3a56f825cd2e11be4b0cf0">GCF::ApplicationServices::loadComponent()</a> method with a component-library name as parameter </li>
<li>Call the <a class="el" href="class_g_c_f_1_1_application_services.html#a9fe06a88ce3a56f825cd2e11be4b0cf0">GCF::ApplicationServices::loadComponent()</a> method with a component pointer ( <code><a class="el" href="class_g_c_f_1_1_component.html" title="Base class for all GCF components.">GCF::Component</a>*</code> ) as parameter. </li>
<li>Call the <a class="el" href="class_g_c_f_1_1_application_services.html#a2d00007fdb8de827c1d47aac03e0d09c">GCF::ApplicationServices::instantiateComponent()</a> method to create an instance of the component from a shared-library and then call <a class="el" href="class_g_c_f_1_1_component.html#a06e3573f06292a5211b81201ced61deb">load()</a> on it.</li>
</ul>
<p>During the load process several events are despatched by GCF to the component. These events can be handled by either reimplementing the <code>QObject::event()</code> method or any of the specialized event handler methods offered as virtual functions in <a class="el" href="class_g_c_f_1_1_component.html">GCF::Component</a>. We recommend doing the latter.</p>
<p>The following video explains the flow of events during component load.</p>
<p> 
<video width="500" controls>
    <source src="../../../Videos/Concepts/Component-Loading.mp4" type="video/mp4">
</video>
<p>If you are unable to view the embedded video above, please click <a href="http://player.vimeo.com/video/78147503" target="_blank">here</a> to view it on the web.</p>
</p>
<dl class="section see"><dt>See also</dt><dd><a class="el" href="class_g_c_f_1_1_component.html#gcf_component_loading">Component loading (or initialization)</a></dd></dl>
<h1><a class="anchor" id="gcf_component_model_5_5"></a>
How component unloading works</h1>
<p>By default all components are unloaded when the application is about to quit. However, components can be explicitly unloaded using any of the following means.</p>
<p>Components can be unloaded using any of the following means</p>
<ul>
<li>Calling the <a class="el" href="class_g_c_f_1_1_component.html#a8c7530baab5694de7676a76eeb50eb3f">unload()</a> method on the component object. </li>
<li>Call the <a class="el" href="class_g_c_f_1_1_application_services.html#ae7f24097c2789e90f0e8abf8308c42ae">GCF::ApplicationServices::unloadComponent()</a> method with a component pointer ( <code><a class="el" href="class_g_c_f_1_1_component.html" title="Base class for all GCF components.">GCF::Component</a>*</code> ) as parameter.</li>
</ul>
<p>During the unload process several events are despatched by GCF to the component. These events can be handled by either reimplementing the <code>QObject::event()</code> method or any of the specialized event handler methods offered as virtual functions in <a class="el" href="class_g_c_f_1_1_component.html">GCF::Component</a>. We recommend doing the latter.</p>
<p>The following video explains the flow of events during component unload.</p>
<p> 
<video width="500" controls>
    <source src="../../../Videos/Concepts/Component-Unloading.mp4" type="video/mp4">
</video>
<p>If you are unable to view the embedded video above, please click <a href="http://player.vimeo.com/video/78152875" target="_blank">here</a> to view it on the web.</p>
</p>
<dl class="section see"><dt>See also</dt><dd><a class="el" href="class_g_c_f_1_1_component.html#gcf_component_unloading">Component unloading (or uninitialization)</a></dd></dl>
<h1><a class="anchor" id="gcf_component_model_6"></a>
Registering objects</h1>
<p>The process of including a pointer to an object into the object tree is called "registering the object". Once registered, the object is available for access from other components. The objects are "exposed", so to speak.</p>
<p> 
<center><div style="border: solid; border-width: 2px; width: 80%; padding: 10px">
Except for the application object, all objects registered with GCF have to be allocated on the heap.
</div></center>
</p>
<p>A component can register its objects in three ways</p>
<ul>
<li>It can list its objects in a content-file and reimplement the <a class="el" href="class_g_c_f_1_1_component.html#a8447de04766d75220159e9db2ceeb5c8">GCF::Component::contentObjectLoadEvent()</a> event handler to load a named object, so that they are included in the object tree.</li>
</ul>
<ul>
<li>You can call <a class="el" href="class_g_c_f_1_1_component.html#ac8791368cb9615392e6c9c2d380034f1">GCF::Component::addContentObject()</a> method anytime after the post-initialization event is delivered to <a class="el" href="class_g_c_f_1_1_component.html#a75422842587613d43844e73fb8ca021d">GCF::Component::initializeEvent()</a>, with object-name and object-pointer as parameters to include the object in the object-tree.</li>
</ul>
<ul>
<li>You can create an instance of <a class="el" href="class_g_c_f_1_1_object_tree_node.html">GCF::ObjectTreeNode</a> under any pre-existing node in the object tree to include a pointer to your <code>QObject</code>.</li>
</ul>
<p>We will now look at each method independently.</p>
<h2><a class="anchor" id="gcf_component_model_61"></a>
Component content file</h2>
<p>While handling the pre-content-load event in <a class="el" href="class_g_c_f_1_1_component.html#a7b9e7071c2f4b483a4ee51b08b70835c">GCF::Component::contentLoadEvent()</a>, components can specify a content file for GCF to process and load. The content file is a XML file whose primary purpose is to provide a list of objects that need to be loaded during <a class="el" href="class_g_c_f_1_1_component.html#a06e3573f06292a5211b81201ced61deb">GCF::Component::load()</a>. A typical content file would look like this</p>
<pre class="fragment">&lt;content&gt;

    &lt;object name="a" /&gt;
    &lt;object name="b" /&gt;
    &lt;object name="c" /&gt;
    &lt;object name="d" /&gt;

&lt;/content&gt;
</pre><p>Basically the content-file contains <code>content</code> XML element as root and a series of <code>object</code> XML elements. Each <code>object</code> XML element must have a name attribute, otherwise it is ignored by GCF. Object names must be unique within the component, otherwise GCF will attempt to make it unique by adding some characters at the end of the name.</p>
<p>The <code>object</code> XML element can contain additional attributes, some of which have implicit meanings. Please read the page on <a class="el" href="gcf_content_xml.html">Content XML File Specification</a> to know more about attributes and their meaning.</p>
<p>Whenever GCF parses a <code>object</code> XML element, it sends a <a class="el" href="class_g_c_f_1_1_content_object_load_event.html">GCF::ContentObjectLoadEvent</a> to the component. Along with this event GCF will send the name of the object in question and a key=value map of all other attributes in the <code>object</code> XML element.</p>
<p>The component can handle this event in <a class="el" href="class_g_c_f_1_1_component.html#a8447de04766d75220159e9db2ceeb5c8">GCF::Component::contentObjectLoadEvent()</a> to</p>
<ul>
<li>actually load the object (as a <code>QObject</code> instance)</li>
</ul>
<p>AND</p>
<ul>
<li>use the <a class="el" href="class_g_c_f_1_1_content_object_load_event.html#ac1016669478dc3d263622aa5cefa70bf">GCF::ContentObjectLoadEvent::setObject()</a> method on the event object, passed as parameter to the event handler, to send back pointer to the <code>QObject</code> that was just loaded</li>
</ul>
<p>After the <a class="el" href="class_g_c_f_1_1_component.html#a8447de04766d75220159e9db2ceeb5c8">GCF::Component::contentObjectLoadEvent()</a> returns, GCF looks for value of the <code>parent</code> attribute. The value of <code>parent</code> attribute has to be a path to an already registered object in the application. If the path corresponds to an object owned by another component, then a <a class="el" href="class_g_c_f_1_1_content_object_merge_event.html">GCF::ContentObjectMergeEvent</a> is sent to that component. This event can be handled in the <a class="el" href="class_g_c_f_1_1_component.html#a1de83ead9a736b7fe19f61626b24a5b6">GCF::Component::contentObjectMergeEvent()</a> of the parent object's component to perform object-merging. Components can customize the way in which merging happens by reimplementing <a class="el" href="class_g_c_f_1_1_component.html#a1de83ead9a736b7fe19f61626b24a5b6">contentObjectMergeEvent()</a>. By default</p>
<ul>
<li><a class="el" href="class_g_c_f_1_1_component.html">GCF::Component</a>'s implementation of the <code>contentObjectMergeEvent()</code> simply makes use of <code>QObject::setParent()</code> to perform the merging.</li>
</ul>
<ul>
<li><a class="el" href="class_g_c_f_1_1_gui_component.html">GCF::GuiComponent</a>'s implementation of <code>contentObjectMergeEvent()</code> takes into account the kind of parent and child that is being merged and performs merging accordingly. For example, if the child is an <code>QAction</code> and parent is a <code>QMenu</code>, it inserts the action as a menu-item in the menu. For a complete list of combinations that are handled, please read the documentation of <a class="el" href="class_g_c_f_1_1_gui_component.html#a862fb78fdba64b956eab4c8a82c89b07">GCF::GuiComponent::contentObjectMergeEvent()</a></li>
</ul>
<ul>
<li><a class="el" href="class_g_c_f_1_1_qml_component.html">GCF::QmlComponent</a>'s implementation of <code>contentObjectMergeEvent()</code> ignores merging between two QML objects.</li>
</ul>
<p>The following video explains the whole process of loading and merging of objects, with the help of an example.</p>
<p> 
<video width="500" controls>
    <source src="../../../Videos/Concepts/Component-Merging.mp4" type="video/mp4">
</video>
<p>If you are unable to view the embedded video above, please click <a href="http://player.vimeo.com/video/78163068" target="_blank">here</a> to view it on the web.</p>
</p>
<h2><a class="anchor" id="gcf_component_model_62"></a>
Using addContentObject() function</h2>
<p>During and after the post-initialization event, components can make use of <a class="el" href="class_g_c_f_1_1_component.html#ac8791368cb9615392e6c9c2d380034f1">GCF::Component::addContentObject()</a> to explicitly register objects with the application.</p>
<h2><a class="anchor" id="gcf_component_model_63"></a>
Explicitly creating object-tree-nodes</h2>
<p>From any part of the application, you can create an instance of <a class="el" href="class_g_c_f_1_1_object_tree_node.html">GCF::ObjectTreeNode</a> under any node in the <code>gAppService-&gt;objectTree()</code>. Example:</p>
<div class="fragment"><div class="line">QObject *<span class="keywordtype">object</span> = createMyNewQObject();</div>
<div class="line"> </div>
<div class="line"><span class="keyword">new</span> <a class="code" href="class_g_c_f_1_1_object_tree_node.html">GCF::ObjectTreeNode</a>(gAppService-&gt;objectTree()-&gt;rootNode(), <span class="stringliteral">&quot;abcd&quot;</span>, object);</div>
<div class="line"> </div>
<div class="line"><span class="comment">// Now the object is registered as abcd under the root-node of the object tree.</span></div>
</div><!-- fragment --><p>While <a class="el" href="gcf_component_model.html#gcf_component_model_62">addContentObject()</a> function can be used to add an object under the node of a component in the object-tree, creating object-tree-nodes by yourself allows you to include your object in any part of the object-tree.</p>
<dl class="section note"><dt>Note</dt><dd>It is not possible to <a class="el" href="gcf_component_model.html#gcf_component_model_63">explicitly create nodes</a> OR use <a class="el" href="gcf_component_model.html#gcf_component_model_62">addContentObject()</a> to add an object and merge it with another object in the applicaiton. Object merging is possible only when you use content-xml files.</dd></dl>
<h1><a class="anchor" id="gcf_component_model_7"></a>
Searching for objects</h1>
<p>The ability to discover objects and functionality from different components is very important. GCF offers two ways for doing this</p>
<ul>
<li><a class="el" href="gcf_component_model.html#gcf_component_model_71">Using gFindObject and gFindObjects</a> </li>
<li><a class="el" href="gcf_component_model.html#gcf_component_model_72">Connecting to nodeAdded() signal of gAppService-&gt;objectTree()</a></li>
</ul>
<h2><a class="anchor" id="gcf_component_model_71"></a>
Using gFindObject and gFindObjects</h2>
<p>Once an object is registered with GCF, it is considered to be "exposed". Exposed objects can be searched by making use of the <a class="el" href="group__gcf__core.html#gab7501f17ab3c80077a3a08364424dda6">gFindObject()</a> method. This method can be used to find objects based on their object path in <a class="el" href="class_g_c_f_1_1_application_services.html#a22657bd136cbf7a285cf0b273a40963a">gAppService-&gt;objectTree()</a> or based on the class or interface type that they implement.</p>
<p>Example:</p>
<div class="fragment"><div class="line"><span class="comment">// Using gFindObject to search an object by its path</span></div>
<div class="line">QObject *itemRegistryObject1 = <a class="code" href="group__gcf__core.html#gab7501f17ab3c80077a3a08364424dda6">gFindObject</a>(<span class="stringliteral">&quot;Application.ItemRegistryComponent.ItemRegistry&quot;</span>);</div>
<div class="line">ItemRegistryClass *itemRegistry1 = qobject_cast&lt;ItemRegistryClass*&gt;(itemRegistryObject1);</div>
<div class="line"> </div>
<div class="line"><span class="comment">// Using gFindObject to search for an object by its class or interface</span></div>
<div class="line">ItemRegistryClass *itemRegistry2 = gFindObject&lt;ItemRegistryClass&gt;();</div>
</div><!-- fragment --><p>You can make use of the <a class="el" href="group__gcf__core.html#gac91a7cc03dfc7dac0f1bf3cc5070cd4b">gFindObjects()</a> method to get a list of all objects of a particular class or interface.</p>
<h2><a class="anchor" id="gcf_component_model_72"></a>
Connecting to nodeAdded() signal of gAppService-&gt;objectTree()</h2>
<p>As mentioned before, every time an object is registered; a node for the same is created and included in the object-tree. The object-tree (of type <a class="el" href="class_g_c_f_1_1_object_tree.html">GCF::ObjectTree</a>) emits a <a class="el" href="class_g_c_f_1_1_object_tree.html#a0a2df3b6342786910574b90b168b1205">GCF::ObjectTree::nodeAdded()</a> signal. This signal can be connected to a slot to get notified whenever an object is included in the object tree. You could then examine the object that just got added and store it in an internal list if required.</p>
<p>Example:</p>
<div class="fragment"><div class="line"><span class="keyword">class </span>ItemRegistryFinder : <span class="keyword">public</span> QObject</div>
<div class="line">{</div>
<div class="line">    Q_OBJECT</div>
<div class="line"> </div>
<div class="line"><span class="keyword">public</span>:</div>
<div class="line">    ItemRegistryFinder(QObject *parent) : QObject(parent) {</div>
<div class="line">        connect(gAppService-&gt;objectTree(),</div>
<div class="line">                SIGNAL(nodeAdded(<a class="code" href="class_g_c_f_1_1_object_tree_node.html">GCF::ObjectTreeNode</a>*,<a class="code" href="class_g_c_f_1_1_object_tree_node.html">GCF::ObjectTreeNode</a>*)),</div>
<div class="line">                <span class="keyword">this</span>,</div>
<div class="line">                SLOT(onNodeAdded(<a class="code" href="class_g_c_f_1_1_object_tree_node.html">GCF::ObjectTreeNode</a>*,<a class="code" href="class_g_c_f_1_1_object_tree_node.html">GCF::ObjectTreeNode</a>*)));</div>
<div class="line">    }</div>
<div class="line"> </div>
<div class="line">    <span class="comment">// ....</span></div>
<div class="line">    Q_SLOT <span class="keywordtype">void</span> onNodeAdded(<a class="code" href="class_g_c_f_1_1_object_tree_node.html">GCF::ObjectTreeNode</a> *parent, <a class="code" href="class_g_c_f_1_1_object_tree_node.html">GCF::ObjectTreeNode</a> *child) {</div>
<div class="line">        Q_UNUSED(parent);</div>
<div class="line">        <span class="keywordflow">if</span>( qobject_cast&lt;ItemRegistryClass*&gt;(child-&gt;<a class="code" href="class_g_c_f_1_1_object_tree_node.html#a293b2658f9a94d7fa45412e724e6c4d5">object</a>()) ) {</div>
<div class="line">            m_itemRegistryObjects.append(child-&gt;<a class="code" href="class_g_c_f_1_1_object_tree_node.html#a293b2658f9a94d7fa45412e724e6c4d5">object</a>());</div>
<div class="line">            <span class="comment">// do something else if needed</span></div>
<div class="line">        }</div>
<div class="line">    }</div>
<div class="line">    <span class="comment">// ...</span></div>
<div class="line"> </div>
<div class="line"><span class="keyword">private</span>:</div>
<div class="line">    <a class="code" href="class_g_c_f_1_1_object_list.html">GCF::ObjectList</a> m_itemRegistryObjects;</div>
<div class="line">};</div>
</div><!-- fragment --><h1><a class="anchor" id="gcf_component_model_8"></a>
How application shut down works</h1>
<p>When an application is about to shut down, it unloads each and every component in the application in the reverse order of their loading. At the end of this cycle the application's event loop is terminated and the <code>main()</code> function returns, causing the application-process to quit.</p>
<h1><a class="anchor" id="gcf_component_model_9"></a>
Suggested reading</h1>
<p>Next, please read the article on <a class="el" href="gcf_getting_started.html">Getting started with GCF</a>. This will help you to understand the GCF 3 concepts in action! </p>
</div></div><!-- contents -->
</div><!-- PageDoc -->
<div class="ttc" id="aclass_g_c_f_1_1_application_html"><div class="ttname"><a href="class_g_c_f_1_1_application.html">GCF::Application</a></div><div class="ttdoc">GCF::Application represents the non-gui, terminal application configuration available in GCF3.</div><div class="ttdef"><b>Definition:</b> Application.h:104</div></div>
<div class="ttc" id="agroup__gcf__core_html_gab7501f17ab3c80077a3a08364424dda6"><div class="ttname"><a href="group__gcf__core.html#gab7501f17ab3c80077a3a08364424dda6">gFindObject</a></div><div class="ttdeci">QObject * gFindObject(const QString &amp;path)</div><div class="ttdef"><b>Definition:</b> Application.h:116</div></div>
<div class="ttc" id="aclass_g_c_f_1_1_object_tree_node_html"><div class="ttname"><a href="class_g_c_f_1_1_object_tree_node.html">GCF::ObjectTreeNode</a></div><div class="ttdoc">Represents a node in GCF::ObjectTree.</div><div class="ttdef"><b>Definition:</b> ObjectTree.h:111</div></div>
<div class="ttc" id="aclass_g_c_f_1_1_object_list_html"><div class="ttname"><a href="class_g_c_f_1_1_object_list.html">GCF::ObjectList</a></div><div class="ttdoc">This class manages a list of live QObject pointers.</div><div class="ttdef"><b>Definition:</b> ObjectList.h:45</div></div>
<div class="ttc" id="aclass_g_c_f_1_1_object_tree_node_html_a293b2658f9a94d7fa45412e724e6c4d5"><div class="ttname"><a href="class_g_c_f_1_1_object_tree_node.html#a293b2658f9a94d7fa45412e724e6c4d5">GCF::ObjectTreeNode::object</a></div><div class="ttdeci">QObject * object() const</div><div class="ttdef"><b>Definition:</b> ObjectTree.cpp:481</div></div>
</div>
</div>
</div>
<div class="footer_content">
<table width="100%" class="footer">
<tr>
<td align="left" width="50%">Copyright &copy; 2013-2019,
 <a class="el" href="http://www.vcreatelogic.com" target="_black">VCreate Logic Private Limited</a></td>
<td align="right" width="50%"><a class="el" href="http://www.vcreatelogic.com/products/gcf" target="_black">GCF - Generic Component Framework</a></td>
</tr>
</table>
</div>
</div>
</body>
</html>
